package game.breeze.socket.util;

import java.awt.Rectangle;
import java.io.BufferedReader;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.io.UnsupportedEncodingException;

public final class Utils {
	private static final java.text.SimpleDateFormat dateFormat = new java.text.SimpleDateFormat("yyyy年MM月dd日 HH:mm:ss");
	private static final java.text.SimpleDateFormat dayDateFormat = new java.text.SimpleDateFormat("yyyyMMdd");
	private static final java.util.Date date = new java.util.Date();
	private static final java.util.Date nowDate = new java.util.Date();

	private Utils() {
	}

	public static String decodeString(byte[] data) {
		return decodeString(data, 0, data.length);
	}

	public static String decodeString(byte[] data, int offset, int count) {
		if (data[offset] < 32) {
			try {
				return new String(data, offset, count, "UTF8");
			} catch (UnsupportedEncodingException e) {
				e.printStackTrace();
			}
		}
		return new String(data, offset, count);
	}

	public static String readLine(InputStream in) throws IOException {
		ByteBuffer buff = new ByteBuffer(256);
		int b = in.read();
		if (b == 10 || b == 13)
			b = in.read();
		while (b > 0) {
			buff.writeByte(b);
			b = in.read();
			if (b == 13 || b == 10)
				break;
		}
		String s = buff.toString().trim();
		return s;
	}

	/**
	 * 从字节缓冲区读取一行 注意：如果到缓冲区的末尾都找不到换行符，则会抛出异常！！！
	 */
	public static String readLine(ByteBuffer in) {
		ByteBuffer buff = new ByteBuffer(in.available());
		int b = in.readUnsignedByte();
		if (b == 10 || b == 13) {
			if (in.available() == 0)
				return "";
			b = in.readUnsignedByte();
		}
		while (b > 0) {
			buff.writeByte(b);
			b = in.readUnsignedByte();
			if (b == 13 || b == 10)
				break;
		}
		String s = buff.toString().trim();
		return s;
	}

	public static String getStackTrace(Throwable e) {
		if (e == null)
			return "no exception";
		ByteArrayOutputStream out = new ByteArrayOutputStream();
		PrintWriter writer = new PrintWriter(new OutputStreamWriter(out));
		e.printStackTrace(writer);
		writer.flush();
		writer.close();
		return out.toString();
	}

	public static int indexOf(byte[] data, byte[] src) {
		int u = data.length - src.length;
		for (int i = 0; i < u; i++) {
			boolean b = true;
			for (int j = 0; j < src.length; j++) {
				b &= data[i + j] == src[j];
				if (!b)
					break;
			}
			if (b)
				return i;
		}
		return -1;
	}

	public static String urlDecode(String src) {
		byte[] data = src.getBytes();
		ByteBuffer buff = new ByteBuffer();
		for (int i = 0; i < data.length; i++) {
			if (data[i] == '+') {
				buff.writeByte(32);
			} else if (data[i] == '%') {
				String str = new String(data, i + 1, 2);
				int ch = Integer.parseInt(str, 16);
				buff.writeByte(ch);
				i += 2;
			} else {
				buff.writeByte(data[i]);
			}
		}
		return buff.toString();
	}

	public static String strDecode(String src) {
		if (src.indexOf('%') < 0 && src.indexOf('+') < 0)
			return src;
		StringBuffer out = new StringBuffer(src.length());
		char ch = 0;
		int count = src.length();
		for (int i = 0; i < count; i++) {
			ch = src.charAt(i);
			if (ch == '%') {
				int index = src.indexOf('%', i + 1);
				String numStr = src.substring(i + 1, index);
				ch = (char) Integer.parseInt(numStr, 16);
				i = index;
			} else if (ch == '+') {
				ch = 32;
			}
			out.append(ch);
		}
		return out.toString();
	}

	public static String strEncode(String src) {
		char ch = 0;
		StringBuffer out = new StringBuffer(src.length() * 5);
		int count = src.length();
		for (int i = 0; i < count; i++) {
			ch = src.charAt(i);
			if (ch > 127 || ch == '%' || ch == '+' || ch == '"' || ch == '\'' || ch == '<' || ch == '>') {
				out.append('%');
				out.append(Integer.toHexString(ch));
				out.append('%');
			} else if (ch == 32) {
				out.append('+');
			} else {
				out.append(ch);
			}
		}
		return out.toString();
	}

	public static void sleep(int delay) {
		try {
			Thread.sleep(delay);
		} catch (InterruptedException e) {
			// e.printStackTrace();
		}
	}

	public static void intersection(Rectangle r1, Rectangle r2, Rectangle r3) {
		int tx1 = r1.x;
		int ty1 = r1.y;
		int rx1 = r2.x;
		int ry1 = r2.y;
		int tx2 = tx1;
		tx2 += r1.width;
		int ty2 = ty1;
		ty2 += r1.height;
		int rx2 = rx1;
		rx2 += r2.width;
		int ry2 = ry1;
		ry2 += r2.height;
		if (tx1 < rx1)
			tx1 = rx1;
		if (ty1 < ry1)
			ty1 = ry1;
		if (tx2 > rx2)
			tx2 = rx2;
		if (ty2 > ry2)
			ty2 = ry2;
		tx2 -= tx1;
		ty2 -= ty1;
		if (tx2 < Integer.MIN_VALUE)
			tx2 = Integer.MIN_VALUE;
		if (ty2 < Integer.MIN_VALUE)
			ty2 = Integer.MIN_VALUE;
		r3.setBounds(tx1, ty1, (int) tx2, (int) ty2);
	}

	@SuppressWarnings({ "unchecked", "rawtypes" })
	public static Object loadObject(Object refObject, String className) {
		try {
			ClassLoader loader = refObject.getClass().getClassLoader();
			Class objClass = loader.loadClass(className);
			return objClass.newInstance();
		} catch (ClassNotFoundException e) {
			e.printStackTrace();
		} catch (IllegalAccessException e) {
			e.printStackTrace();
		} catch (InstantiationException e) {
			e.printStackTrace();
		}
		return null;
	}

	@SuppressWarnings({ "unchecked", "rawtypes" })
	public static Object loadObject(String className) {
		try {
			Class objClass = Class.forName(className);
			return objClass.newInstance();
		} catch (ClassNotFoundException e) {
			e.printStackTrace();
		} catch (IllegalAccessException e) {
			e.printStackTrace();
		} catch (InstantiationException e) {
			e.printStackTrace();
		}
		return null;
	}

	public static String readUTFFile(String filename) {
		File file = new File(filename);
		return readUTFFile(file);
	}

	public static String readUTFFile(File file) {
		if (!file.exists() || file.isDirectory())
			return null;
		try {
			BufferedReader in = new BufferedReader(new InputStreamReader(new FileInputStream(file), "UTF8"));
			StringBuffer fileBuffer = new StringBuffer();
			String line;
			while ((line = in.readLine()) != null) {
				// System.out.println("line:" + line);
				fileBuffer.append(line + "\r\n");
			}

			fileBuffer.deleteCharAt(0);
			// fileBuffer.delete(fileBuffer.length() - 2, fileBuffer.length() -
			// 1);
			// System.out.println(fileBuffer.toString());
			// InputStream in = new FileInputStream(file);
			// byte[] data = new byte[in.available()];
			// in.read(data);
			// in.close();
			// String content = new String();
			// return new String(fileBuffer.toString().getBytes(), "UTF-8");
			return fileBuffer.toString();// .substring(1,
											// fileBuffer.toString().length());
		} catch (IOException e) {
			e.printStackTrace();
		}
		return null;
	}

	public static byte[] readFile(String filename) {
		File file = new File(filename);
		return readFile(file);
	}

	public static byte[] readFile(File file) {
		if (!file.exists() || file.isDirectory())
			return null;
		try {
			InputStream in = new FileInputStream(file);
			byte[] data = new byte[in.available()];
			in.read(data);
			in.close();
			return data;
		} catch (IOException e) {
			e.printStackTrace();
		}
		return null;
	}

	public static void writeFile(String filename, byte[] data) {
		try {
			FileOutputStream out = new FileOutputStream(filename);
			out.write(data);
			out.close();
		} catch (IOException e) {
			e.printStackTrace();
		}
	}

	public static String getCurrentTime() {
		return getCurrentTime(System.currentTimeMillis());
	}

	public static String getCurrentTime(long time) {
		date.setTime(time);
		return dateFormat.format(date);
	}

	public static String getTimeString(long time) {
		date.setTime(time);
		return dateFormat.format(date);
	}

	public static int compareDay(long timeMillions) {
		nowDate.setTime(System.currentTimeMillis());
		date.setTime(timeMillions);

		String str1 = dayDateFormat.format(date);
		String str2 = dayDateFormat.format(nowDate);

		return str1.compareTo(str2);
	}
}